//---------------------------------------------------------------------------
//     Greenplum Database
//     Copyright (C) 2010 Greenplum, Inc.
//     Copyright (C) 2021, HuaWei Group Holding Limited
//
//     @filename:
//          CParseHandlerTableShareScan.cpp
//
//     @doc:
//          Implementation of the SAX parse handler class for parsing table scan operators.
//---------------------------------------------------------------------------

#include "naucrates/dxl/parser/CParseHandlerTableShareScan.h"
#include "naucrates/dxl/parser/CParseHandlerFactory.h"
#include "naucrates/dxl/parser/CParseHandlerFilter.h"
#include "naucrates/dxl/parser/CParseHandlerProjList.h"
#include "naucrates/dxl/parser/CParseHandlerProperties.h"
#include "naucrates/dxl/parser/CParseHandlerTableDescr.h"
#include "naucrates/dxl/parser/CParseHandlerUtils.h"

#include "naucrates/dxl/operators/CDXLOperatorFactory.h"
#include "naucrates/dxl/operators/CDXLPhysicalExternalScan.h"

using namespace spqdxl;


XERCES_CPP_NAMESPACE_USE

//---------------------------------------------------------------------------
//     @function:
//          CParseHandlerTableShareScan::CParseHandlerTableShareScan
//
//     @doc:
//          Constructor
//
//---------------------------------------------------------------------------
CParseHandlerTableShareScan::CParseHandlerTableShareScan
     (
     CMemoryPool *mp,
     CParseHandlerManager *parse_handler_mgr,
     CParseHandlerBase *parse_handler_root
     )
     :
     CParseHandlerPhysicalOp(mp, parse_handler_mgr, parse_handler_root),
     m_dxl_op(NULL)
{
}


//---------------------------------------------------------------------------
//     @function:
//          CParseHandlerTableShareScan::StartElement
//
//     @doc:
//          Invoked by Xerces to process an opening tag
//
//---------------------------------------------------------------------------
void
CParseHandlerTableShareScan::StartElement
     (
     const XMLCh* const, // element_uri,
     const XMLCh* const element_local_name,
     const XMLCh* const, // element_qname
     const Attributes& // attrs
     )
{
     StartElement(element_local_name, EdxltokenPhysicalTableShareScan);
}

//---------------------------------------------------------------------------
//     @function:
//          CParseHandlerTableShareScan::StartElement
//
//     @doc:
//          Start element helper function
//
//---------------------------------------------------------------------------
void
CParseHandlerTableShareScan::StartElement
     (
     const XMLCh* const element_local_name,
     Edxltoken token_type
     )
{
     if (0 != XMLString::compareString(CDXLTokens::XmlstrToken(token_type), element_local_name))
     {
          CWStringDynamic *str = CDXLUtils::CreateDynamicStringFromXMLChArray(m_parse_handler_mgr->GetDXLMemoryManager(), element_local_name);
          SPQOS_RAISE(spqdxl::ExmaDXL, spqdxl::ExmiDXLUnexpectedTag, str->GetBuffer());
     }

     SPQOS_ASSERT (EdxltokenPhysicalTableShareScan == token_type);
     m_dxl_op = SPQOS_NEW(m_mp) CDXLPhysicalTableShareScan(m_mp);

     // create child node parsers in reverse order of their expected occurrence

     // parse handler for table descriptor
     CParseHandlerBase *table_descr_parse_handler = CParseHandlerFactory::GetParseHandler(m_mp, CDXLTokens::XmlstrToken(EdxltokenTableDescr), m_parse_handler_mgr, this);
     m_parse_handler_mgr->ActivateParseHandler(table_descr_parse_handler);

     // parse handler for the filter
     CParseHandlerBase *filter_parse_handler = CParseHandlerFactory::GetParseHandler(m_mp, CDXLTokens::XmlstrToken(EdxltokenScalarFilter), m_parse_handler_mgr, this);
     m_parse_handler_mgr->ActivateParseHandler(filter_parse_handler);

     // parse handler for the proj list
     CParseHandlerBase *proj_list_parse_handler = CParseHandlerFactory::GetParseHandler(m_mp, CDXLTokens::XmlstrToken(EdxltokenScalarProjList), m_parse_handler_mgr, this);
     m_parse_handler_mgr->ActivateParseHandler(proj_list_parse_handler);

     //parse handler for the properties of the operator
     CParseHandlerBase *prop_parse_handler = CParseHandlerFactory::GetParseHandler(m_mp, CDXLTokens::XmlstrToken(EdxltokenProperties), m_parse_handler_mgr, this);
     m_parse_handler_mgr->ActivateParseHandler(prop_parse_handler);

     // store child parse handlers in array
     this->Append(prop_parse_handler);
     this->Append(proj_list_parse_handler);
     this->Append(filter_parse_handler);
     this->Append(table_descr_parse_handler);
}

//---------------------------------------------------------------------------
//     @function:
//          CParseHandlerTableShareScan::EndElement
//
//     @doc:
//          Invoked by Xerces to process a closing tag
//
//---------------------------------------------------------------------------
void
CParseHandlerTableShareScan::EndElement
     (
     const XMLCh* const, // element_uri,
     const XMLCh* const element_local_name,
     const XMLCh* const // element_qname
     )
{
     EndElement(element_local_name, EdxltokenPhysicalTableShareScan);
}

//---------------------------------------------------------------------------
//     @function:
//          CParseHandlerTableShareScan::EndElement
//
//     @doc:
//          End element helper function
//
//---------------------------------------------------------------------------
void
CParseHandlerTableShareScan::EndElement
     (
     const XMLCh* const element_local_name,
     Edxltoken token_type
     )
{
     if (0 != XMLString::compareString(CDXLTokens::XmlstrToken(token_type), element_local_name))
     {
          CWStringDynamic *str = CDXLUtils::CreateDynamicStringFromXMLChArray(m_parse_handler_mgr->GetDXLMemoryManager(), element_local_name);
          SPQOS_RAISE(spqdxl::ExmaDXL, spqdxl::ExmiDXLUnexpectedTag, str->GetBuffer());
     }

     // construct node from the created child nodes
     CParseHandlerProperties *prop_parse_handler = dynamic_cast<CParseHandlerProperties *>((*this)[0]);
     CParseHandlerProjList *proj_list_parse_handler = dynamic_cast<CParseHandlerProjList*>((*this)[1]);
     CParseHandlerFilter *filter_parse_handler = dynamic_cast<CParseHandlerFilter *>((*this)[2]);
     CParseHandlerTableDescr *table_descr_parse_handler = dynamic_cast<CParseHandlerTableDescr*>((*this)[3]);

     SPQOS_ASSERT(NULL != table_descr_parse_handler->GetDXLTableDescr());

     // set table descriptor
     CDXLTableDescr *table_descr = table_descr_parse_handler->GetDXLTableDescr();
     table_descr->AddRef();
     m_dxl_op->SetTableDescriptor(table_descr);

     m_dxl_node = SPQOS_NEW(m_mp) CDXLNode(m_mp, m_dxl_op);
     // set statictics and physical properties
     CParseHandlerUtils::SetProperties(m_dxl_node, prop_parse_handler);

     // add constructed children
     AddChildFromParseHandler(proj_list_parse_handler);
     AddChildFromParseHandler(filter_parse_handler);

#ifdef SPQOS_DEBUG
     m_dxl_op->AssertValid(m_dxl_node, false /* validate_children */);
#endif // SPQOS_DEBUG

     // deactivate handler
     m_parse_handler_mgr->DeactivateHandler();
}

// EOF

